#ifndef OPHIES_DATAMODEL_H
#define OPHIES_DATAMODEL_H

#include "irm_types.h"
#include "irm_objectrequest.h"
#include "json/value.h"
#include "irm_search.h"
#include <QObject>
#include <QHash>
#include <QList>
#include <iostream>


#define ATTR_DCM_STUDY_COUNT 22
#define ATTR_DCM_SERIES_COUNT 14
#define ATTR_DCM_INSTANCE_COUNT 12
#define ATTR_DOCSET_COUNT 32
#define PAITNET_ATTR_COUNT 9


namespace ophies {

class RequestCallback;

class DataModel : public QObject
{
	Q_OBJECT

public:

	DataModel(DataModelType type, QObject *parent);
	virtual ~DataModel();

	static  const char* ATTRS_PATIENT[];
	static  const char* ATTRS_DOCSET[];
	static  const char* ATTRS_DCM_STUDY[];
	static  const char* ATTRS_DCM_SERIES[];
	static  const char* ATTRS_DCM_INSTANCE[];

private:
	DataModelType m_type;

protected:
	QHash<QString, QString> *m_attributes;

signals:

protected:
	virtual void onSave();

public:
	QString getAttr(QString attr_name, QString defaultValue="Error");
	void setAttr(QString attr_name, QString value);

public:
    void fromJson(Json::Value &value);
	bool save();

public:
	DataModelType getDataModelType();
    bool equal(DataModel* another);



};


class DcmSeries;
class DcmStudy;

class DcmInstance : public DataModel
{
public:
    DcmInstance(QObject *parent);
    virtual ~DcmInstance();

private:
    QString download_url;
    QString wado_url;
    DcmSeries *m_parentSeries;

public:
    QString get_download_url();
    QString get_wado_url();
    void setParentDcmSeries(DcmSeries* series);
    DcmSeries* getParentDcmSeries();

public:
	void set_download_url(QString);
	void set_wado_url(QString);

	// auto generated getters
public:
    QString get_dcm_instance_key();
    QString get_vgroup_key();
    QString get_sop_instance_uid();
    QString get_sop_class_uid();
    QString get_dcm_series_key();
    QString get_dcm_study_key();
    QString get_instance_no();
    QString get_content_dttm();
    QString get_instance_size();
    QString get_created_dttm();
    QString get_deleted_dttm();
    QString get_self_url();
    QString get_study_instance_uid();
    QString get_series_instance_uid();

};

class DcmSeries : public DataModel
{
public:
    DcmSeries(QObject *parent);
    virtual ~DcmSeries();

private:
    QList<DcmInstance*> *m_dcm_instances;
    DcmStudy* m_parentStudy;

public:
    void appendInstance(DcmInstance* i);
    QList<DcmInstance*>* getAllDcmInstances();
    DcmInstance* getDcmInstanceByInstanceKey(QString);
    DcmInstance* getDcmInstanceBySopInstanceUid(QString);

    void setParentDcmStudy(DcmStudy* study);
    DcmStudy* getParentDcmStudy();



// getters
public:
    QString get_dcm_series_key();
    QString get_vgroup_key();
    QString get_series_instance_uid();
    QString get_dcm_study_key();
    QString get_modality();
    QString get_series_no();
    QString get_series_dttm();
    QString get_series_desc();
    QString get_bodypart();
    QString get_series_size();
    QString get_instance_count();
    QString get_created_dttm();
    QString get_deleted_dttm();
    QString get_self_url();
};

class DcmStudy : public DataModel
{
public:
	DcmStudy(QObject *parent);
	virtual ~DcmStudy();

private:
    QList<DcmSeries*> *m_dcm_series;

public:
    void appendSeries(DcmSeries* se);
    QList<DcmSeries*>* getAllDcmSeries();
    DcmSeries* getDcmSeriesBySeriesKey(QString);
    DcmSeries* getDcmSeriesBySeriesInstanceUid(QString);

// auto generated getters
public:
    QString get_dcm_study_key();
    QString get_vgroup_key();
    QString get_study_instance_uid();
    QString get_patient_key();
    QString get_patient_id();
    QString get_patient_name();
    QString get_patient_sex();
    QString get_patient_birth_dttm();
    QString get_patient_age();
    QString get_patient_weight();
    QString get_patient_size();
    QString get_study_id();
    QString get_study_dttm();
    QString get_accession_no();
    QString get_study_desc();
    QString get_study_size();
    QString get_series_count();
    QString get_instance_count();
    QString get_created_dttm();
    QString get_updated_dttm();
    QString get_deleted_dttm();
    QString get_self_url();

private: // for test
    QList<DcmSeries*> *abnormal_series;
};


class Docset : public DataModel
{
public:
	Docset(QObject *parent);
	virtual ~Docset();

// getters
public:
    QString get_docset_key();
    QString get_vgroup_key();
    QString get_vgroup_id();
    QString get_vgroup_id_type();
    QString get_vgroup_name();
    QString get_docset_uid();
    QString get_docset_class_uid();
    QString get_docset_group_uid();
    QString get_filter_key();
    QString get_filter_uid();
    QString get_filter_class_uid();
    QString get_filter_name();
    QString get_patient_key();
    QString get_patient_id_value();
    QString get_patient_name();
    QString get_docset_created_dttm();
    QString get_docset_deleted_dttm();
    QString get_xds_docset_key();
    QString get_metadata_xml();
    QString get_docset_uuid();
    QString get_source_id();
    QString get_content_type_code_value();
    QString get_content_type_coding_scheme();
    QString get_content_type_code_meaning();
    QString get_docset_status();
    QString get_docset_title();
    QString get_docset_comments();
    QString get_submit_dttm();
    QString get_xds_docset_created_dttm();
    QString get_xds_docset_deleted_dttm();
    QString get_document_count();
    QString get_self_url();
};

class Patient : public DataModel
{
public:
	Patient(QObject *parent);
	virtual ~Patient();

	// auto generated getters
public:
	QString get_patient_key();
	QString get_patient_id_value();
	QString get_patient_name();
	QString get_patient_sex();
	QString get_patient_birth_dttm();
	QString get_related_patient_key();
	QString get_created_dttm();
	QString get_deleted_dttm();
	QString get_self_url();
};




}
#endif // DATAMODEL_H
